import datarover from "../../lib/datarover.mjs";
import thin_render from "../../lib/thin_render.mjs";
import { renderRow } from "./render-row.mjs";

/**
 * 渲染表格主体部分
 * @param {HTMLElement} table - 表格元素
 * @param {Array} data - 表格数据
 * @param {Object} template - 模板配置对象
 * @param {string} mode - 渲染模式(read/edit)
 */
export function renderBody(table, data, template, mode) {
  if (template.groupdatapath) {
    // 处理分组数据
    let groups = Array.isArray(data) ? data : [];
    groups.forEach((group) => {
      let tbody = document.createElement("tbody");
      table.appendChild(tbody);
      tbody.thin_data = group;

      if (template.grouprowtemplate) {
        let tr = document.createElement("tr");
        tbody.appendChild(tr);
        if (typeof template.grouprowtemplate === "string") {
          thin_render(tr, {
            td: template.grouprowtemplate,
            class: "fixed",
            a: {
              colspan: 3,
            },
          });
        }
      }

      // 从分组中获取数据
      let groupData = datarover(group, template.datapath) || [];
      renderRowGroup(tbody, groupData, template, mode);
    });
  } else {
    // 处理普通数据
    let tbody = document.createElement("tbody");
    table.appendChild(tbody);
    renderRowGroup(tbody, Array.isArray(data) ? data : [], template, mode);
  }

  // 添加重渲染回调到 template
  template.rerender = (tbody, data) => {
    renderRowGroup(tbody, data, template, mode);
  };
}

/**
 * 渲染行组
 * @param {HTMLElement} tbody - tbody元素
 * @param {Array} data - 数据数组
 * @param {Object} template - 模板配置对象
 * @param {string} mode - 渲染模式
 */
function renderRowGroup(tbody, data, template, mode) {
  // 拖拽排序支持
  if (template.rowdrag) {
    tbody.ondragstart = (e) => {
      let tr = e.target;
      let receiver = e.target.closest("tbody");
      let controller = new AbortController();

      // 允许放置
      receiver.addEventListener(
        "dragover",
        (e) => {
          e.preventDefault();
        },
        { signal: controller.signal }
      );

      // 处理放置
      receiver.addEventListener(
        "drop",
        (e) => {
          let target = e.target.closest("tr");
          receiver.insertBefore(tr, target.nextSibling);
          controller.abort();

          // 收集新的数据顺序
          let result = [];
          receiver.querySelectorAll("tr").forEach((tr) => {
            if (tr.thin_data && tr.thin_rowindex !== undefined) {
              result.push(tr.thin_data);
            }
          });
          template.rowdrag(result);
        },
        { signal: controller.signal }
      );

      e.stopPropagation(); // 阻止事件向上传递，防止冒泡。
    };
  }

  // 渲染数据行
  if (Array.isArray(data)) {
    tbody.thin_rowdata = data;
    let rowindex = 0;
    data.forEach((row) => {
      let tr = document.createElement("tr");
      tr.thin_data = row;
      tr.thin_rowindex = rowindex;
      tbody.appendChild(tr);

      // 设置拖拽属性
      if (template.rowdrag) tr.setAttribute("draggable", true);

      // 设置行样式
      if (template.rowclass) {
        if (typeof template.rowclass === "function") {
          tr.classList.add(template.rowclass(row));
        } else {
          tr.classList.add(template.rowclass);
        }
      }

      // 渲染行内容
      renderRow({ tr, row, template, mode });
      rowindex++;
    });
  }

  // 渲染插入行
  renderInsertRow(tbody, template, mode);
}

function renderInsertRow(tbody, template, mode) {
  if (template.rowinsert && mode === "edit") {
    const tr = document.createElement("tr");
    tbody.appendChild(tr);
    tr.setAttribute("insertrow", true);
    tr.thin_data = template.rowinsert_defaultvalue
      ? { ...template.rowinsert_defaultvalue }
      : {};

    renderRow({
      tr,
      template,
      mode,
      insert: true,
    });
  }
}
